﻿--Inport: PMEngine, PrivateDB, ProfileDB, GlobalDB
local PMEngine, L, PrivateDB, ProfileDB, GlobalDB = unpack(select(2, ...)); 
local CB = PMEngine:GetModule('CastBars')

local MODNAME = "PlayerCastBar"
local Player = PMEngine:NewModule(MODNAME)
CB.Player = Player

----------------------------
-- Upvalues
-- GLOBALS: CastingBarFrame
local unpack = unpack
local UnitChannelInfo = UnitChannelInfo

local db, getOptions, castBar


function Player:Initialize()
	self.db = CB:Merge(PMEngine.db.castbars.CastBarTemplateDefaults, PMEngine.db.castbars.player)
	db = self.db

	self:SetEnabledState(Player)

	self.Bar = CB.CastBarTemplate:new(self, "player", MODNAME, "Player", db)
	castBar = self.Bar.Bar
	self:MyEnable()
end

function Player:UpdateDB()
	self.db = CB:Merge(PMEngine.db.castbars.CastBarTemplateDefaults, PMEngine.db.castbars.player)
	db = self.db

	self:ApplySettings()
end

function Player:MyEnable()
	self.Bar:RegisterEvents()
	self:ApplySettings()
end

function Player:MyDisable()
	self.Bar:UnregisterEvents()
	self.Bar:Hide()
end

function Player:ApplySettings()
	db = self.db

	-- obey the hideblizz setting no matter if disabled or not
	if db.hideblizz then
		CastingBarFrame.RegisterEvent = function() end
		CastingBarFrame:UnregisterAllEvents()
		CastingBarFrame:Hide()
	else
		CastingBarFrame.RegisterEvent = nil
		CastingBarFrame:UnregisterAllEvents()
		CastingBarFrame:RegisterEvent("UNIT_SPELLCAST_START")
		CastingBarFrame:RegisterEvent("UNIT_SPELLCAST_STOP")
		CastingBarFrame:RegisterEvent("UNIT_SPELLCAST_FAILED")
		CastingBarFrame:RegisterEvent("UNIT_SPELLCAST_INTERRUPTED")
		CastingBarFrame:RegisterEvent("UNIT_SPELLCAST_DELAYED")
		CastingBarFrame:RegisterEvent("UNIT_SPELLCAST_CHANNEL_START")
		CastingBarFrame:RegisterEvent("UNIT_SPELLCAST_CHANNEL_STOP")
		CastingBarFrame:RegisterEvent("UNIT_SPELLCAST_CHANNEL_UPDATE")
		CastingBarFrame:RegisterEvent("UNIT_SPELLCAST_INTERRUPTIBLE")
		CastingBarFrame:RegisterEvent("UNIT_SPELLCAST_NOT_INTERRUPTIBLE")
		CastingBarFrame:RegisterEvent("PLAYER_ENTERING_WORLD")
	end
	
	self.Bar:SetConfig(db)
	if self:IsEnabled() then
		self.Bar:ApplySettings()
	end
end

function Player:Unlock()
	self.Bar:Unlock()
end

function Player:Lock()
	self.Bar:Lock()
end

----------------------------
-- Cast Bar Hooks

function Player:OnHide()
	local Latency = PMEngine:GetModule("Latency",true)
	if Latency then
		if Latency:IsEnabled() and Latency.lagbox then
			Latency.lagbox:Hide()
			Latency.lagtext:Hide()
		end
	end
end

local sparkfactory = {
	__index = function(t,k)
		local spark = castBar:CreateTexture(nil, 'OVERLAY', nil)
		t[k] = spark
		spark:SetTexture([[Interface\CastingBar\UI-CastingBar-Spark]]);
		--spark:SetVertexColor(unpack(CB.db.sparkcolor))
		spark:SetBlendMode('ADD')
		spark:SetWidth(12)
		spark:SetHeight(db.h*2.2)
		return spark
	end
}
local barticks = setmetatable({}, sparkfactory)

local function setBarTicks(ticknum)
	if( ticknum and ticknum > 0) then
		local delta = ( (PandemoniuMUI_Bar1:GetWidth()-4) / ticknum )
		for k = 1,ticknum do
			local t = barticks[k]
			t:ClearAllPoints()
			t:SetPoint("CENTER", castBar, "LEFT", delta * k, 0 )
			t:Show()
		end
	else
		barticks[1].Hide = nil
		for i=1,#barticks do
			barticks[i]:Hide()
		end
	end
end

-- TODO: this will need updates for Cataclysm
local channelingTicks = {
	-- warlock
	[GetSpellInfo(1120)] = 5, -- drain soul
	[GetSpellInfo(689)] = 5, -- drain life
	[GetSpellInfo(5740)] = 4, -- rain of fire
	-- druid
	[GetSpellInfo(740)] = 4, -- Tranquility
	[GetSpellInfo(16914)] = 10, -- Hurricane
	-- priest
	[GetSpellInfo(15407)] = 3, -- mind flay
	[GetSpellInfo(48045)] = 5, -- mind sear
	[GetSpellInfo(47540)] = 2, -- penance
	-- mage
	[GetSpellInfo(5143)] = 5, -- arcane missiles
	[GetSpellInfo(10)] = 5, -- blizzard
	[GetSpellInfo(12051)] = 4, -- evocation
}

local function getChannelingTicks(spell)
	if not db.showticks then
		return 0
	end
	
	return channelingTicks[spell] or 0
end

function Player:UNIT_SPELLCAST_START(bar, unit)
	if bar.channeling then
		local spell = UnitChannelInfo(unit)
		bar.channelingTicks = getChannelingTicks(spell)
		setBarTicks(bar.channelingTicks)
	else
		setBarTicks(0)
	end
end

function Player:UNIT_SPELLCAST_STOP(bar, unit)
	setBarTicks(0)
end

function Player:UNIT_SPELLCAST_FAILED(bar, unit)
	setBarTicks(0)
end

function Player:UNIT_SPELLCAST_INTERRUPTED(bar, unit)
	setBarTicks(0)
end

function Player:UNIT_SPELLCAST_DELAYED(bar, unit)

end
